<template>
    <div class="text-dom-select-wrap" :class="wrapClass" :style="style" ref="textDomSelectWrap">
        <div class="text-dom-select-wrap-inner">
            <template v-if="slots.default">
                <div v-for="(vnode, idx) in rows" :key="idx" class="text-dom-select-item">
                    <component :is="vnode" @mousedown.prevent/>
                </div>
            </template>
        </div>
    </div>
</template>
  
<script setup>
import { ref, reactive, onMounted, onBeforeUnmount, nextTick, useSlots, computed } from 'vue'
const slots = useSlots();

const props = defineProps({
    area: Object,
    // 出现的位置
    placement: {
        type: String,
        default: 'top'
    },
    // 出现位置的偏移量
    offset: {
        type: Number,
        default: 12
    }
})
const rows = computed(() => {
    return slots.default()?.[0]?.children?.[0]?.children
})

const wrapClass = ref(props.placement)

const textDomSelectWrap = ref()
let resize_obersver = null
let el_posi_obersver = null
const style = ref({
    top: 0,
})

let info = {}

const handler = () => {
    const viewHeight = window.innerHeight
    const { top: selectTop, bottom: selectBottom, height: selectHeight } = textDomSelectWrap.value.getBoundingClientRect()
    const { top: areaTop, bottom: areaBottom, height: areaHeight } = props.area.getBoundingClientRect()
    // 计算输入框距离屏幕下方的距离
    const bottom = viewHeight - areaTop - areaHeight - props.offset
    // console.log('resize', selectTop, selectBottom, areaTop, areaBottom, selectHeight, areaHeight, viewHeight)
    if (props.placement === 'top') {
        requestAnimationFrame(() => {
            if (areaTop > selectHeight + props.offset) {
                wrapClass.value = 'top'
                style.value.top = `-${ selectHeight + props.offset }px`
            } else {
                wrapClass.value = 'bottom'
                style.value.top = `${ props.offset + areaHeight }px`
            }
        })
    } else {
        requestAnimationFrame(() => {
            if (bottom > selectHeight + props.offset) {
                wrapClass.value = 'bottom'
                style.value.top = `${ props.offset + areaHeight }px`
            } else {
                wrapClass.value = 'top'
                style.value.top = `-${ selectHeight + props.offset }px`
            }
        })
    }
}

onMounted(() => {
    // const { top: selectTop, bottom: selectBottom, height: selectHeight } = textDomSelectWrap.value.getBoundingClientRect()
    // const { top: areaTop, bottom: areaBottom, height: areaHeight } = props.area.getBoundingClientRect()
    // info = {
    //     selectTop,
    //     selectBottom,
    //     selectHeight,
    //     areaTop,
    //     areaBottom,
    //     areaHeight
    // }
    // 监测窗口改变，重新计算他的位置，是在上面还是下面
    resize_obersver = new ResizeObserver(() => {
        nextTick(() => {
            handler()
        })
    })
    resize_obersver.observe(document.body)

    // el_posi_obersver = new MutationObserver(() => {
    //     console.log('变了')
    // })
    // el_posi_obersver.observe(textDomSelectWrap.value, { attributes: true, characterData: true })
    window.addEventListener('scroll', () => {
        console.log(111)
    })
})

onBeforeUnmount(() => {
    console.log('beforeUnmount')
    resize_obersver.disconnect()
})
</script>

<style scoped lang="scss">
.text-dom-select-wrap {
    padding: 8px;
    border-radius: 8px;
    position: relative;
    top: 12px;
    background: #fff;
    filter: drop-shadow(0 0 10px rgba(0,0,0,.1));
    position: absolute;
    box-sizing: border-box;
    width: 100%;
    .text-dom-select-wrap-inner {
        max-height: 200px;
        overflow-y: auto;
        .text-dom-select-item {
            height: 32px;
            font-size: 14px;
            line-height: 32px;
            transition: all ease-in-out .2s;
            cursor: pointer;
            &:hover {
                padding-left: 4px;
                background: #ecf5ff;
            }
        }
    }
    
    &.top::before {
        content: '';
        position: absolute;
        bottom: -16px;
        left: 50%;
        transform: translateX(-50%);
        width: 0;
        height: 0;
        border: 8px solid transparent;
        border-top-color: #fff;
    }
    &.bottom::after {
        content: '';
        position: absolute;
        top: -16px;
        left: 50%;
        transform: translateX(-50%);
        width: 0;
        height: 0;
        border: 8px solid transparent;
        border-bottom-color: #fff;
    }
}

</style>
